package com.yuuko.yuukoapi.repository.system

import com.yuuko.yuukoapi.common.constant.StatusEnum
import com.yuuko.yuukoapi.model.system.Menus
import com.yuuko.yuukoapi.model.system.children
import com.yuuko.yuukoapi.model.system.fetchBy
import com.yuuko.yuukoapi.model.system.id
import com.yuuko.yuukoapi.model.system.meta
import com.yuuko.yuukoapi.model.system.name
import com.yuuko.yuukoapi.model.system.parentId
import com.yuuko.yuukoapi.model.system.path
import com.yuuko.yuukoapi.model.system.roles
import com.yuuko.yuukoapi.model.system.status
import com.yuuko.yuukoapi.model.system.users
import com.yuuko.yuukoapi.model.system.`users?`
import org.babyfish.jimmer.spring.repository.KRepository
import org.babyfish.jimmer.sql.kt.ast.expression.eq
import org.babyfish.jimmer.sql.kt.ast.expression.isNull
import org.babyfish.jimmer.sql.kt.ast.expression.ne
import org.springframework.stereotype.Repository

/**
 * <p>
 * MenusRepository 接口
 * </p>
 *
 * @author yuuko
 * @date 2025-06-20
 */
@Repository
interface MenusRepository : KRepository<Menus, String> {
    fun findAllTree(): List<Menus> {
        return sql.createQuery(Menus::class) {
            where(table.parentId.isNull())
            select(table.fetchBy {
                allScalarFields()
                `children*`()
            })
        }.execute()
    }

    fun findTreeByUserId(userId: String): List<Menus> {
        return sql.createQuery(Menus::class) {
            where(table.parentId.isNull())
            where(table.roles {
                `users?`.id eq userId
            })
            select(table.fetchBy {
                allScalarFields()
                `children*`()
            })
        }.execute()
    }

    fun existsOtherByName(name: String?, id: String?): Boolean {
        return sql.createQuery(Menus::class) {
            where(table.name eq name)
            where(table.id ne id)
            select(table.id)
        }.exists()
    }

    fun existsOtherByPath(path: String?, id: String?): Boolean {
        return sql.createQuery(Menus::class) {
            where(table.path eq path)
            where(table.id ne id)
            select(table.id)
        }.exists()
    }

    fun findAllByUserIdAndStatusIsActivated(userId: String): List<Menus> {
        return sql.createQuery(Menus::class) {
            where(table.roles {
                users {
                    id eq userId
                }
            })
            where(table.status eq StatusEnum.ENABLED.value)
            select(table)
        }.execute()
    }

}

